Passa al contenuto principale

Istruzioni processore x86

Le seguenti tabelle sono per riferimento rapido: sono utili per la programmazione pratica, ma omettono molteplici dettagli che serve sapere, e che trovate nel resto del materiale.

Si ricorda che, nella sintassi GAS/AT&T, le istruzioni sono nel formato opcode source destination. Nella colonna notazione, si indicano con [bwl] le istruzioni che richiedono la specifica delle dimensioni. Quando la dimensione è deducibile dai registri utilizzati, questi suffissi si possono omettere.

Per gli operandi, si indica con con r un registro (come in mov %eax, %ebx); con m un indirizzo di memoria (immediato, come in mov numero, %eax, o tramite registro, come in mov (%esi), %eax, o ancora con indice, come in mov matrice(%esi, %ecx, 4)); con i un valore immediato (come in mov $0, %eax).

Si ricorda che non tutte le combinazioni sono permesse nell'architettura x86: nessuna istruzione generale supporta l'indicazione di entrambi gli operandi in memoria (cioè, non si può scrivere movl x, y o mov (%eax), (%ebx)). Fanno eccezione le istruzioni stringa come la movs, usando operandi impliciti.

Spostamento di dati

IstruzioneNome estesoNotazioneComportamento
movMovemov[bwl] r/m/i, r/mScrive il valore sorgente nel destinatario. Non modifica ZF.
leaLoad Effective Addresslea a, rScrive l'indirizzo nel registro destinatario.
xchgExchangexchg[bwl] r/m, r/mScambia il valore del sorgente con quello del destinatario.
cbwConvert Byte to WordcbwEstende il contenuto di %al su %ax, interpretandone il contenuto come intero.
cwdeConvert Word to DoublewordcwdeEstende il contenuto di %ax su %eax, interpretandone il contenuto come intero.
pushPush onto the Stackpush[wl] r/m/iAggiunge il valore sorgente in cima allo stack (destinatario implicito).
popPop from the Stackpop[wl] r/mRimuove un valore dallo stack (sorgente implicito) lo scrive nel destinatario.

Aritmetica

IstruzioneNome estesoNotazioneComportamento
addAdditionadd[bwl] r/m/i, r/mSomma sorgente e destinatario, scrive il risultato sul destinatario. Valido sia per naturali che interi. Aggiorna CF e OF.
subSubtractionsub[bwl] r/m/i, r/mSottrae il sorgente dal destinatario, scrive il risultato sul destinatario. Valido sia per naturali che interi. Aggiorna CF e OF.
adcAddition with Carryadc[bwl] r/m/i, r/mSomma sorgente, destinatario e CF, scrive il risultato sul destinatario. Valido sia per naturali che interi. Aggiorna CF e OF.
sbbSubtraction with Borrowsub[bwl] r/m/i, r/mSottrae il sorgente e CF dal destinatario, scrive il risultato sul destinatario. Valido sia per naturali che interi. Aggiorna CF e OF.
incIncrementinc[bwl] r/mSomma 1 (sorgente implicito) al destinatario. Non aggiorna CF.
decDecrementdec[bwl] r/mSottrae 1 (sorgente implicito) al destinatario. Non aggiorna CF.
negNegationneg[bwl] r/mSostituisce il destinatario con il suo opposto. Aggiorna OF.

Le seguenti istruzioni hanno operandi e destinatari impliciti, che variano in base alla dimensione dell'operazione. Usano in oltre composizioni di più registri: useremo %dx_%ax per indicare un valore i cui bit più significativi sono scritti in %dx e quelli meno significativi in %ax.

IstruzioneNome estesoNotazioneComportamento
mulUnsigned Multiply, 8 bitmulb r/mCalcola su 16 bit il prodotto tra naturali del sorgente e %al, scrive il risultato su %ax. Se il risultato non è riducibile a 8 bit, mette CF e OF a 1, altrimenti a 0.
mulUnsigned Multiply, 16 bitmulw r/mCalcola su 32 bit il prodotto tra naturali del sorgente e %ax, scrive il risultato su %dx_%ax. Se il risultato non è riducibile a 16 bit, mette CF e OF a 1, altrimenti a 0.
mulUnsigned Multiply, 32 bitmull r/mCalcola su 64 bit il prodotto tra naturali del sorgente e %eax, scrive il risultato su %edx_%eax. Se il risultato non è riducibile a 32 bit, mette CF e OF a 1, altrimenti a 0.
imulSigned Multiply, 8 bitimulb r/mCalcola su 16 bit il prodotto tra interi del sorgente e %al, scrive il risultato su %ax. Se il risultato non è riducibile a 8 bit, mette CF e OF a 1, altrimenti a 0.
imulSigned Multiply, 16 bitimulw r/mCalcola su 32 bit il prodotto tra interi del sorgente e %ax, scrive il risultato su %dx_%ax. Se il risultato non è riducibile a 16 bit, mette CF e OF a 1, altrimenti a 0.
imulSigned Multiply, 32 bitimull r/mCalcola su 64 bit il prodotto tra interi del sorgente e %eax, scrive il risultato su %edx_%eax. Se il risultato non è riducibile a 32 bit, mette CF e OF a 1, altrimenti a 0.
IstruzioneNome estesoNotazioneComportamento
divUnsigned Divide, 8 bitdivb r/mCalcola su 8 bit la divisione tra naturali tra %ax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %al e il resto su %ah. Se il quoziente non è rappresentabile su 8 bit, causa crash del programma.
divUnsigned Divide, 16 bitdivw r/mCalcola su 16 bit la divisione tra naturali tra %dx_%ax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %ax e il resto su %dx. Se il quoziente non è rappresentabile su 16 bit, causa crash del programma.
divUnsigned Divide, 32 bitdivl r/mCalcola su 32 bit la divisione tra naturali tra %edx_%eax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %eax e il resto su %edx. Se il quoziente non è rappresentabile su 32 bit, causa crash del programma.
idivSigned Divide, 8 bitidivb r/mCalcola su 8 bit la divisione tra interi tra %ax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %al e il resto su %ah. Se il quoziente non è rappresentabile su 8 bit, causa crash del programma.
idivSigned Divide, 16 bitidivw r/mCalcola su 16 bit la divisione tra interi tra %dx_%ax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %ax e il resto su %dx. Se il quoziente non è rappresentabile su 16 bit, causa crash del programma.
idivSigned Divide, 32 bitidivl r/mCalcola su 32 bit la divisione tra interi tra %edx_%eax (dividendo implicito) e il sorgento (divisore). Scrive il quoziente su %eax e il resto su %edx. Se il quoziente non è rappresentabile su 32 bit, causa crash del programma.

Logica binaria

Le seguenti istruzioni operano bit a bit: data per esempio la and, l'i-esimo bit del risultato è l'and logico tra gli i-esimi bit di sorgente e destinatario.

IstruzioneNotazioneComportamento
notnot[bwl] r/mSostituisce il destinatario con la sua negazione.
andand r/m/i, r/mCalcola l'and logico tra sorgente e destinatario, scrive il risultato sul destinatario.
oror r/m/i, r/mCalcola l'or logico tra sorgente e destinatario, scrive il risultato sul destinatario.
xorxor r/m/i, r/mCalcola lo xor logico tra sorgente e destinatario, scrive il risultato sul destinatario.

Traslazione e Rotazione

IstruzioneNome estesoNotazioneComportamento
shlShift Logical Leftshl[bwl] i/r r/mSia n l'operando sorgente, esegue lo shift a sinistra del destinatario n volte. In ciascuno shift, il bit più significativo viene lasciato in CF. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
salShift Arithmetic Leftsal[bwl] i/r r/mSia n l'operando sorgente, esegue lo shift a sinistra del destinatario n volte. Se il bit più significativo ha cambiato valore almeno una volta, imposta OF a 1. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
shrShift Logical Rightshr[bwl] i/r r/mSia n l'operando sorgente, esegue lo shift a destra del destinatario n volte, impostando a 0 gli n bit più significativi. In ciascuno shift, il bit più significativo viene lasciato in CF. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
sarShift Arithmetic Rightsar[bwl] i/r r/mSia n l'operando sorgente e s il valore del bit più significativo del destinatario, esegue lo shift a destra del destinatario n volte, impostando a s gli n bit più significativi. Il bit più significativo tra quelli rimossi viene lasciato in CF. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
rolRotate Leftrol[bwl] i/r r/mSia n l'operando sorgente, esegue la rotazione a sinistra del destinatario n volte. In ciascuna rotazione, il bit più significativo viene sia lasciato in CF sia ricopiato al posto del bit meno significativo. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
rorRotate Rightror[bwl] i/r r/mSia n l'operando sorgente, esegue la rotazione a destra del destinatario n volte. In ciascuna rotazione, il bit meno significativo viene sia lasciato in CF sia ricopiato al posto del bit più significativo. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
rclRotate with Carry Leftrcl[bwl] i/r r/mSia n l'operando sorgente, esegue la rotazione con carry a sinistra del destinatario n volte. In ciascuna rotazione, il bit più significativo viene lasciato in CF, mentre il valore di CF viene ricopiato al posto del bit meno significativo. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.
rcrRotate with Carry Rightrcr[bwl] i/r r/mSia n l'operando sorgente, esegue la rotazione con carry a destra del destinatario n volte. In ciascuna rotazione, il bit meno significativo viene lasciato in CF, mentre il valore di CF viene ricopiato al posto del bit più significativo. Come registro sorgente si può utilizzare solo %cl. Il sorgente può essere omesso, in quel caso n=1.

Controllo di flusso

IstruzioneNome estesoNotazioneComportamento
jmpUnconditional Jumpjmp m/rSalta incondizionatamente all'indirizzo specificato.
callCall Procedurecall m/rChiamata a procedura all'indirizzo specificato. Salva l'indirizzo della prossima istruzione nello stack, così che il flusso corrente possa essere ripreso con una ret.
retReturn from ProcedureretRitorna ad un flusso di esecuzione precedente, rimuovendo dallo stack l'indirizzo precedentemente salvato da una call.

La tabella seguente elenca i salti condizionati. I salti condizionati usano i flag per determinare se la condizione di salto è vera. Per un uso sempre coerente, assicurarsi che l'istruzione di salto segua immediatamente una cmp, o altre istruzioni che non hanno modificano i flag dopo la cmp. Dati gli operandi della cmp ed una condizione c, per esempio c = "maggiore o uguale", la condizione è vera se destinatario c sorgente. Nella tabella che segue, quando ci si riferisce ad un confronto fra sorgente e destinatario si intendono gli operandi della cmp precedente.

IstruzioneNome estesoNotazioneComportamento
cmpCompare Two Operandscmp[bwl] r/m/i, r/mConfronta i due operandi e aggiorna i flag di conseguenza.
jeJump if Equalje mSalta se destinatario == sorgente.
jneJump if Not Equaljne mSalta se destinatario != sorgente.
jaJump if Aboveja mSalta se, interpretandoli come naturali, destinatario > sorgente.
jaeJump if Above or Equaljae mSalta se, interpretandoli come naturali, destinatario >= sorgente.
jbJump if Belowjb mSalta se, interpretandoli come naturali, destinatario < sorgente.
jbeJump if Below or Equaljbe mSalta se, interpretandoli come naturali, destinatario <= sorgente.
jgJump if Greaterjg mSalta se, interpretandoli come interi, destinatario > sorgente.
jgeJump if Greater or Equaljge mSalta se, interpretandoli come interi, destinatario >= sorgente.
jlJump if Lessjl mSalta se, interpretandoli come interi, destinatario < sorgente.
jleJump if Less or Equaljle mSalta se, interpretandoli come interi, destinatario <= sorgente.
jzJump if Zerojz mSalta se ZF è 1.
jnzJump if Not Zerojnz mSalta se ZF è 0.
jcJump if Carryjc mSalta se CF è 1.
jncJump if Not Carryjnc mSalta se CF è 0.
joJump if Overflowjo mSalta se OF è 1.
jnoJump if Not Overflowjno mSalta se OF è 0.
jsJump if Signjs mSalta se SF è 1.
jnsJump if Not Signjns mSalta se SF è 0.

Operazioni condizionali

Per alcune operazioni tipiche, sono disponibili istruzioni specifiche il cui comportamento dipende dai flag e, quindi, dal risultato di una precedente cmp. Anche qui, quando ci si riferisce ad un confronto fra sorgente e destinatario si intendono gli operandi della cmp precedente.

La famiglia di istruzioni loop supportano i cicli condizionati più tipici. Rimangono d'interesse didattico come istruzioni specializzate ma, curiosamente, nei processori moderni sono generalmente meno performanti degli equivalenti che usino dec,cmp e salti condizionati.

IstruzioneNome estesoNotazioneComportamento
loopUnconditional Looploop mDecrementa %ecx e salta se il risultato è (ancora) diverso da 0.
loopeLoop if Equalloope mDecrementa %ecx e salta se entrambe le condizioni sono vere: 1)%ecx è (ancora) diverso da 0, 2) destinatario == sorgente.
loopneLoop if Not Equalloopne mDecrementa %ecx e salta se entrambe le condizioni sono vere: 1)%ecx è (ancora) diverso da 0, 2) destinatario != sorgente.
loopzLoop if Zeroloopz mDecrementa %ecx e salta se entrambe le condizioni sono vere: 1)%ecx è (ancora) diverso da 0, 2) ZF è 1.
loopnzLoop if Not Zeroloopnz mDecrementa %ecx e salta se entrambe le condizioni sono vere: 1)%ecx è (ancora) diverso da 0, 2) ZF è 0.

La famiglia di istruzioni set permettono di salvare il valore di un confronto in un registro o locazione di memoria. Tale operando può essere solo da 1 byte.

IstruzioneNome estesoNotazioneComportamento
seteSet if Equalsete r/mImposta l'operando a 1 se destinatario == sorgente, a 0 altrimenti.
setneSet if Not Equalsetne r/mImposta l'operando a 1 se destinatario != sorgente, a 0 altrimenti.
setaSet if Aboveseta r/mImposta l'operando a 1 se, interpretandoli come naturali, destinatario > sorgente, a 0 altrimenti.
setaeSet if Above or Equalsetae r/mImposta l'operando a 1 se, interpretandoli come naturali, destinatario >= sorgente, a 0 altrimenti.
setbSet if Belowsetb r/mImposta l'operando a 1 se, interpretandoli come naturali, destinatario < sorgente, a 0 altrimenti.
setbeSet if Below or Equalsetbe r/mImposta l'operando a 1 se, interpretandoli come naturali, destinatario <= sorgente, a 0 altrimenti.
setgSet if Greatersetg r/mImposta l'operando a 1 se, interpretandoli come interi, destinatario > sorgente, a 0 altrimenti.
setgeSet if Greater or Equalsetge r/mImposta l'operando a 1 se, interpretandoli come interi, destinatario >= sorgente, a 0 altrimenti.
setlSet if Lesssetl r/mImposta l'operando a 1 se, interpretandoli come interi, destinatario < sorgente, a 0 altrimenti.
setleSet if Less or Equalsetle r/mImposta l'operando a 1 se, interpretandoli come interi, destinatario <= sorgente, a 0 altrimenti.
setzSet if Zerosetz r/mImposta l'operando a 1 se ZF è 1, a 0 altrimenti.
setnzSet if Not Zerosetnz r/mImposta l'operando a 1 se ZF è 0, a 0 altrimenti.
setcSet if Carrysetc r/mImposta l'operando a 1 se CF è 1, a 0 altrimenti.
setncSet if Not Carrysetnc r/mImposta l'operando a 1 se CF è 0, a 0 altrimenti.
setoSet if Overflowseto r/mImposta l'operando a 1 se OF è 1, a 0 altrimenti.
setnoSet if Not Overflowsetno r/mImposta l'operando a 1 se OF è 0, a 0 altrimenti.
setsSet if Signsets r/mImposta l'operando a 1 se SF è 1, a 0 altrimenti.
setnsSet if Not Signsetns r/mImposta l'operando a 1 se SF è 0, a 0 altrimenti.
IstruzioneNome estesoNotazioneComportamento
cmoveMove if Equalcmove r/m rEsegue la mov se destinatario == sorgente, altrimenti non fa nulla.
cmovneMove if Not Equalcmovne r/mEsegue la mov se destinatario != sorgente, altrimenti non fa nulla.
cmovaMove if Abovecmova r/mEsegue la mov se, interpretandoli come naturali, destinatario > sorgente, altrimenti non fa nulla.
cmovaeMove if Above or Equalcmovae r/mEsegue la mov se, interpretandoli come naturali, destinatario >= sorgente, altrimenti non fa nulla.
cmovbMove if Belowcmovb r/mEsegue la mov se, interpretandoli come naturali, destinatario < sorgente, altrimenti non fa nulla.
cmovbeMove if Below or Equalcmovbe r/mEsegue la mov se, interpretandoli come naturali, destinatario <= sorgente, altrimenti non fa nulla.
cmovgMove if Greatercmovg r/mEsegue la mov se, interpretandoli come interi, destinatario > sorgente, altrimenti non fa nulla.
cmovgeMove if Greater or Equalcmovge r/mEsegue la mov se, interpretandoli come interi, destinatario >= sorgente, altrimenti non fa nulla.
cmovlMove if Lesscmovl r/mEsegue la mov se, interpretandoli come interi, destinatario < sorgente, altrimenti non fa nulla.
cmovleMove if Less or Equalcmovle r/mEsegue la mov se, interpretandoli come interi, destinatario <= sorgente, altrimenti non fa nulla.
cmovzMove if Zerocmovz r/mEsegue la mov se ZF è 1, altrimenti non fa nulla.
cmovnzMove if Not Zerocmovnz r/mEsegue la mov se ZF è 0, altrimenti non fa nulla.
cmovcMove if Carrycmovc r/mEsegue la mov se CF è 1, altrimenti non fa nulla.
cmovncMove if Not Carrycmovnc r/mEsegue la mov se CF è 0, altrimenti non fa nulla.
cmovoMove if Overflowcmovo r/mEsegue la mov se OF è 1, altrimenti non fa nulla.
cmovnoMove if Not Overflowcmovno r/mEsegue la mov se OF è 0, altrimenti non fa nulla.
cmovsMove if Signcmovs r/mEsegue la mov se SF è 1, altrimenti non fa nulla.
cmovnsMove if Not Signcmovns r/mEsegue la mov se SF è 0, altrimenti non fa nulla.

Istruzioni stringa

Le istruzioni stringa sono ottimizzate per eseguire operazioni tipiche su vettori in memoria. Hanno esclusivamente operandi impliciti, che rende la specifica delle dimensioni non opzionale.

IstruzioneNome estesoNotazioneComportamento
cldClear Direction FlagcldImposta DF a 0, implicando che le istruzioni stringa procederanno per indirizzi crescenti.
stdSet Direction FlagstdImposta DF a 1, implicando che le istruzioni stringa procederanno per indirizzi decrescenti.
lodsLoad Stringlods[bwl]Legge 1/2/4 byte all'indirizzo in %esi e lo scrive in %al/%ax/%eax. Se DF è 0, incrementa %esi di 1/2/4, se è 1 lo decrementa.
stosStore Stringstos[bwl]Legge il valore in %al/%ax/%eax e lo scrive nei 1/2/4 byte all'indirizzo in %edi. Se DF è 0, incrementa %edi di 1/2/4, se è 1 lo decrementa.
movsMove String to Stringmovs[bwl]Legge 1/2/4 byte all'indirizzo in %esi e lo scrive nei 1/2/4 byte all'indirizzo in %edi. Se DF è 0, incrementa %edi di 1/2/4, se è 1 lo decrementa.
cmpsCompare Stringscmps[bwl]Confronta gli 1/2/4 byte all'indirizzo in %esi (sorgente) con quelli all'indirizzo in %edi (destinatario). Aggiorna i flag così come fa cmp.
scasScan Stringscas[bwl]Confronta %al/%ax/%eax (sorgente) con gli 1/2/4 byte all'indirizzo in %edi (destinatario). Aggiorna i flag così come fa cmp.

Repeat Instruction

Le istruzioni stringa possono essere ripetute senza controllo di programma, usando il prefisso rep.

IstruzioneNome estesoNotazioneComportamento
repUnconditional Repeat Instructionrep [opcode]Dato n il valore in %ecx, ripete l'operazione opcode n volte, decrementando %ecx fino a 0. Compatibile con lods, stos, movs.
repeRepeat Instruction if Equalrepe [opcode]Dato n il valore in %ecx, decrementa %ecx e ripete l'operazione opcode finché 1) %ecx è (ancora) diverso da 0, e 2) gli operandi di questa ripetizione erano uguali. Compatibile con cmps e scas.
repneRepeat Instruction if Not Equalrepne [opcode]Dato n il valore in %ecx, decrementa %ecx e ripete l'operazione opcode finché 1) %ecx è (ancora) diverso da 0, e 2) gli operandi di questa ripetizione erano disuguali. Compatibile con cmps e scas.

Altre istruzioni

IstruzioneNome estesoNotazioneComportamento
nopNo OperationnopNon cambia lo stato del processore in alcun modo, eccetto per il registro %eip.

Le seguenti istruzioni sono di interesse didattico ma non per le esercitazioni, in quanto richiedono privilegi di esecuzione.

IstruzioneNome estesoNotazioneComportamento
inInput from Portin r/i rLegge da una porta di input ad un registro.
outOutput to Portout r r/iScrive da un registro ad una porta di output.
insInput String from Portins[bwl]Legge 1/2/4 byte dalla porta di input indicata in %dx e li scrive nei 1/2/4 byte all'indirizzo in %edi.
outsOutput String to Portouts[bwl]Legge 1/2/4 byte all'indirizzo indicato da %esi e li scrive alla porta di output indicata in %dx.
hltHalthltBlocca ogni operazione del processore.